<?php
include_once "function_obj_analyse.php";
include_once "function_base_xml_class.php";

class CSecFilter extends base_xml_class 
{
	function __construct()
	{
		$this->root_path = "/MINI/SECURITY/POLICY/FILTERS";
		$this->node_name = "FILTER";
		$this->key_array = array("Name", "InDev", "OutDev", "SrcAddr", "DstAddr", "Pro_L7", "Filter_Word","Mark_Set", "Log",
			   		 "Srv", "Time", "Target", "Enabled");
	}

	function Apply()
	{
		$iptables = "/usr/local/bin/iptables  ";
	
		$log = '';
		$command = $iptables. " -F USERFILTER ; ";
		$command.= $iptables. " -t nat -F ANTIVIRUS ; ";
		$ext_command = $iptables. " -F PROXYSERVER ;";
		
		$ret_list = $this->get_list();
		foreach ($ret_list as $ret)
		{
			// ------ Enabled ------
			if ($ret['Enabled'] != 1) {
				continue;
			}

			// ------ Table ------
			$table = " -A USERFILTER ";
			
			// ------ Active ------
			$operate = "";
			$value_xml = "";
			$value_xml = $ret['Target'];
			if ($value_xml == "DROP" || $value_xml == "ACCEPT"){
				$operate = " -j ". $value_xml;
				$log = ' -j LOG --log-prefix "FILTER_LOG" ';
			}	
			else if ($value_xml == "FILTER") // key work filter.
			{
				$operate = " -m string --algo bm --string ". base64_decode($ret['Filter_Word']). " ";
				$log = ' -j LOG --log-prefix "KEYWORD_LOG" ';
			}
			else if ($value_xml == "MARK") 	// mark some policy.
			{
				$table = " -t mangle -A PREROUTING ";
				$operate = " -j MARK --set-mark ". $ret['Mark_Set']. " ";
				$log = ' -j LOG --log-prefix "SETMARK_LOG" ';
			}
			else if ($value_xml == "ANTI_VIRUS") 
			{
				$table = " -t nat -A ANTIVIRUS ";

				if ($ret['Srv'] == "UE9QMw==" || // POP3
				    $ret['Srv'] == "U01UUA==")	 // SMTP
				{
					$operate = " -j REDIRECT --to-port 8110 ";
					$ext_command .= $iptables. " -A PROXYSERVER -p tcp --dport 8110 -j ACCEPT;";
					//print "[POP3||SMTP]". $ext_command;
				}
				if ($ret['Srv'] == "SFRUUA==") 	// HTTP
				{
					$operate = " -j REDIRECT --to-port 8080 ";
					$ext_command .= $iptables. " -A PROXYSERVER -p tcp --dport 8080 -j ACCEPT;";
					//print "[HTTP]". $ext_command;
				}
				if ($ret['Srv'] == "RlRQ")	// FTP
				{
					$operate = " -j REDIRECT --to-port 2121 ";
					$ext_command .= $iptables. " -A PROXYSERVER -p tcp --dport 2121 -j ACCEPT;";
					//print "[FTP]". $ext_command;
				}
				$log = ' -j LOG --log-prefix "VIRUS_LOG" ';
			}
			
			// ------ In dev ------
			$value_xml = "";
			$value_xml = $ret['InDev'];
			$indev = ($value_xml == '' || $value_xml == 'All')?(" "):(" -i ". $value_xml. " ");

			// ------ Out dev ------
			$value_xml = "";
			$value_xml = $ret['OutDev'];
			$outdev = ($value_xml == ''|| $value_xml == 'All')?(" "):(" -o ". $value_xml. " ");
			
			// ------ Protocol for L7 ------
			$value_xml = "";
			$value_xml = $ret['Pro_L7'];
			if ($value_xml == '' || $value_xml == 'All') {
				$pro_l7 = "";
			}
			else {
				include_once "function_obj_protocol.php";
				$pro = new CProtocol ();
				$pro_tmp = $pro->get_item_by_name($value_xml);
				foreach ($pro_tmp as $pl){
					$pro_l7 = " -m layer7 --l7proto ". $pl['Protocol']. " ";
				}
			}
			
			// ------ Service ------
			$value_xml = "";
			$value_xml = $ret['Srv'];
			$srv_list = GetServiceList($value_xml);
			//print_r($srv_list);

			// ------ Source address ------
			$value_xml = "";
			$value_xml = $ret['SrcAddr'];
			
			$src_list = GetSourceIpList($value_xml);
			//print_r($src_list);
			// ------ Des address ------
			$value_xml = "";
			$value_xml = $ret['DstAddr'];
			
			$dst_list = GetDestIpList($value_xml);
			//print_r($dst_list);

			$value_xml = "";
			$value_xml = $ret['Time'];
			$time = GetTimeString($value_xml);
			//print $time;

			foreach ($srv_list as $srv) {
				foreach( $src_list as $src){
					foreach ($dst_list as $dst){
						if ($ret['Log'] == 1){	
							$command .= $iptables. $table. $time. $indev. $src. $srv. $outdev. $pro_l7.  $dst. $log. ";";
						}
						$command .= $iptables. $table. $time. $indev. $src. $srv. $outdev. $pro_l7. $dst. $operate. ";";
					}
				}
			}
		}	
		//print $command;
		//print $ext_command;

		$ret = shell_exec($command);
		$ret = shell_exec($ext_command);
		return $ret;
	}
}

$root_path = "/MINI/SECURITY/POLICY/FILTERS";
$root_path_tmp = "/MINI/SECURITY/POLICY/FILTERS";
$iptables = "/usr/local/bin/iptables  ";

function GetXmlSecObjectByName($name)
{
	$ret_array = GetXmlSecObjectList();
    
        foreach ($ret_array as $ret)
        {   
                if ($ret['Name'] == $name)
                        return $ret;
        }   
        return NULL;

}

function GetXmlSecObjectByNumber($n)
{
	global $root_path_tmp;
	$query_string = $root_path_tmp. "/FILTER"."[". $n. "]";
	$key_array = array("Name", "InDev", "OutDev", "SrcAddr", "DstAddr", "Pro_L7", "Filter_Word","Mark_Set", "Log",
			   "Srv", "Time", "Target", "Enabled");
	$list = GetAttributList($query_string, $key_array);
	$list[0]["Filter_Word"] = base64_decode($list[0]["Filter_Word"]);
	$r = $list[0];
	return $r;

}
function GetXmlSecFilterList()
{
	global $root_path_tmp;
	$query_string = $root_path_tmp. "/FILTER";
	$key_array = array("Name", "InDev", "OutDev", "SrcAddr", "DstAddr", "Pro_L7", "Filter_Word", "Mark_Set", "Log",
			   "Srv", "Time", "Target", "Enabled");
	$list = GetAttributList($query_string, $key_array);
	for ($i = 0; $i < count($list); $i ++)
	{
		$list[$i]["Filter_Word"] = base64_decode($list[$i]["Filter_Word"]);
	}
	return $list;
}

function GetXmlNumberSecFilters()
{
	global $root_path;
	$query_string = $root_path. "/FILTER";
	return GetNumberOfNode($query_string);
}

function DelXmlSpecialOneSecObject($name)
{
	global $root_path;

	$query_string = $root_path. "/FILTER[@Name='". $name. "']";
	DelSpecialNode($query_string);
	ApplySecFilterRule();
}

function AppendXmlSecOneFilter($in_array)
{
	global $root_path;
        $node_name = "FILTER";
	$query_string = $root_path;
	$in_array['FilterType'] = "1";
	$in_array['Filter_Word'] = base64_encode($in_array['Filter_Word']);
	AppendAllAttrOfNode($query_string, $node_name, $in_array);
	ApplySecFilterRule();

}

function InsertXmlSecOneFilter($number, $in_array)
{
	global $root_path;
	$node_name = "FILTER";
	$query_string_from = $root_path. '/FILTER['. $number. ']';
	//print $query_string_from;
	InsertOneNode($query_string_from, $node_name, $in_array);
	ApplySecFilterRule();
}

function SetXmlSecOneFilter($in_array, $number)
{
	global $root_path;
	$in_array['Type'] = "1";
	$query_string = $root_path. "/FILTER[". $number. "]";
	$in_array['Filter_Word'] = base64_encode($in_array['Filter_Word']);
	EditAllAttrOfNode($query_string, $in_array);
	ApplySecFilterRule();
}

function MoveXmlOneSecFilter($from, $to)
{
	global $root_path;
	$query_string_from = $root_path.  "/FILTER". "[". $from. "]";
	$query_string_to= $root_path. "/FILTER". "[". $to. "]";
	$query_string_number= $root_path. "/FILTER";
	
	if ($from == $to)
		return SUCCESS;

	$number = GetXmlNumberSecFilters();
	if ($from > $number || $to > $number)
		return ERR_VALUE;

	if ($from > $to)
	{
		MoveFrontOneNode($query_string_from, $query_string_to);
	}
	else
	{
		$number = GetXmlNumberSecFilters();
		if ($to < $number)
		{
			$query_string_to= $root_path. "/FILTER". "[". ($to + 1 ). "]";
			MoveFrontOneNode($query_string_from, $query_string_to);
		}
		else
		{
			MoveEndOneNode($query_string_from, $query_string_to);
		}
	}
	ApplySecFilterRule();
	return SUCCESS;
}

function DelXmlAllSecFilters()
{
	global $root_path;
	$query_string = $root_path. "/FILTER";
	DelSpecialNode($query_string);
	FlushAllFilterRule();
}
function FlushAllFilterRule()
{
	$iptables = "/usr/local/bin/iptables  ";
	$command = "";
	$command1 = $iptables. " -t nat -F USERFILTER; ";
	$command2 = $iptables. " -t mangle -F PREROUTING; ";
	$command = $command1. $command2;
	//print $command;
	$ret = shell_exec($command);
	return $ret;
}

function FlushProxyServerFilterRule()
{
	$iptables = "/usr/local/bin/iptables  ";
	$command = "";
	$command = $iptables. " -F PROXYSERVER;";
	//print $command;
	$ret = shell_exec($command);
	return $ret;
}

function ApplySecFilterRule()
{
	include_once "function_sys_license.php";
	$license = CheckSysLicenseForRule();
	//$license = TRUE;
	if ($license == FALSE)
	{
		return ;
	}

	FlushAllFilterRule();
	FlushProxyServerFilterRule();
	ApplySecFilterRule_One();
	
	return ;
}
function ApplySecFilterRule_One()
{
	$iptables = "/usr/local/bin/iptables  ";
	
	$ret_list = GetXmlSecFilterList();
	
	$log = '';
	//$key_array = array("Name", "InDev", "OutDev", "SrcAddr", "DstAddr", 
	//		   "Srv", "Time", "Target", "Enabled");
	$command = "";

	foreach ($ret_list as $ret)
	{
		
		//print $ret['Enabled'];
		if ($ret['Enabled'] == 0)
		{
			continue;
		}
		if ($ret['Log'] == 1){
			$log = ' -j LOG --log-prefix "Mini FILTER" ';
		}
		else
			$log = '';
		// ------ Table ------
		$table = " -A USERFILTER ";
		
		// ------ Active ------
		$value_xml = "";
		$value_xml = $ret['Target'];
		if ($value_xml == "ANTI_VIRUS")
		{
			if ($ret['Srv'] == "AntiVirus_POP3" || $ret['Srv'] == "AntiVirus_SMTP")
			{
				$operate = " -j REDIRECT --to-port 8110 ";
				//$ext_command .= $iptables. " -A PROXYSERVER -p tcp --dport 8110 -j ACCEPT;";
			}
			if ($ret['Srv'] == "AntiVirus_HTTP")
			{
				$operate = " -j REDIRECT --to-port 8080 ";
				//$ext_command .= $iptables. " -A PROXYSERVER -p tcp --dport 8080 -j ACCEPT;";
			}
			if ($ret['Srv'] == "AntiVirus_FTP")
			{
				$operate = " -j REDIRECT --to-port 2121 ";
				//$ext_command .= $iptables. " -A PROXYSERVER -p tcp --dport 2121 -j ACCEPT;";
			}
		}
		else if ($value_xml == "FILTER") // key work filter.
		{
			$operate = " -m string --algo bm --string ". $ret['Filter_Word']. " ";
		}
		else if ($value_xml == "MARK") 	// mark some policy.
		{
			$operate = " -j MARK --set-mark ". $ret['Mark_Set']. " ";
			$table = " -t mangle -A PREROUTING ";
		}
		else
			$operate = " -j ". $value_xml;

		// ------ In dev ------
		$value_xml = "";
		$value_xml = $ret['InDev'];
		$indev = ($value_xml == '' || $value_xml == 'All')?(" "):(" -i ". $value_xml. " ");

		// ------ Out dev ------
		$value_xml = "";
		$value_xml = $ret['OutDev'];
		$outdev = ($value_xml == ''|| $value_xml == 'All')?(" "):(" -o ". $value_xml. " ");
		
		// ------ Protocol for L7 ------
		$value_xml = "";
		$value_xml = $ret['Pro_L7'];
		if ($value_xml == '' || $value_xml == 'All')
		{
			$pro_l7 = "";
		}
		else
		{
			include_once "function_obj_protocol.php";
			$pro = new CProtocol ();
			$pro_tmp = $pro->get_item_by_name($value_xml);
			$pro_l7 = " -m layer7 --l7proto ". $pro_tmp['Protocol']. " ";
			//print $pro_l7;
		}
			
		// ------ Service ------
		$value_xml = "";
		$value_xml = $ret['Srv'];

		if ($value_xml == '' || $value_xml == 'All')
		{
			$srvtype = "";
		}
		else
		{	
			$src_srv_port = "";
			$dst_srv_port = "";
			$srv_ret_list = GetRealServiceValueByName($value_xml);
			foreach ($srv_ret_list as $srv_ret)
			{
				if ($srv_ret['Protocol'] == '')
					continue;
				
				if ($srv_ret['Protocol'] == '1')
				{
				 	$srvtype = " -p icmp ";
				}
				else if ($srv_ret['Protocol'] == '6' || $srv_ret['Protocol'] == '17' )
				{
					if ($srv_ret['SrcStartPort'] != "" || $srv_ret['SrcEndPort'] != "" )
					{
						$src_srv_port .= " --sport ";
						$src_srv_port .= $srv_ret['SrcStartPort'];	
						$src_srv_port .= ":";
						$src_srv_port .= $srv_ret['SrcEndPort'];
						$src_srv_port .= " ";
					}
					if ($srv_ret['DstStartPort'] != "" || $srv_ret['DstEndPort'] != "" )
					{
						$dst_srv_port .= " --dport ";
						$dst_srv_port .= $srv_ret['DstStartPort'];	
						$dst_srv_port .= ":";
						$dst_srv_port .= $srv_ret['DstEndPort'];
						$dst_srv_port .= " ";
					}
					if ($srv_ret['Protocol'] == '6')
					{
						$srvtype = " -p tcp ";
					}
					if ($srv_ret['Protocol'] == '17')
					{
						$srvtype = " -p udp ";
					}
					$srvtype .= $src_srv_port. $dst_srv_port;
				}
				else // Other integer !
				{
					$srvtype = " -p ". $srv_ret['Protocol']. " ";
				}
			}
		}
		
		// ------ Source address ------
		$value_xml = "";
		$value_xml = $ret['SrcAddr'];

		if ($value_xml == ''|| $value_xml == 'All')
		{
			$src_temp = array ("IpString" => " ", "IpType" => -1);
			$src_ret_list = array( $src_temp);
		}
		else
		{
			$src_ret_list = GetRealNetValueByName($value_xml);
		}
		
		// ------ Des address ------
		$value_xml = "";
		$value_xml = $ret['DstAddr'];
		
		if  ($value_xml == ''|| $value_xml == 'All')
		{
			$dst_temp = array ("IpString" => " ", "IpType" => -1);
			$dst_ret_list = array( $dst_temp);
		}
		else
		{
			$dst_ret_list = GetRealNetValueByName($value_xml);
		}
		
		foreach ($src_ret_list as $src_ret)
		{
			if ($src_ret["IpString"] == NULL)
			{
				continue;
			}
			
			if ($src_ret["IpType"] == 1 || $src_ret["IpType"] == 2)
			{
				$srcaddr = " -s ".$src_ret["IpString"];
			}
			else if ($src_ret["IpType"] == 0)
			{
				$srcaddr = " -m iprange --src-range ". $src_ret["IpString"];
			}
			else
			{
				$srcaddr = " ";
			}

			foreach ($dst_ret_list as $dst_ret)
			{
				if ($dst_ret["IpString"] == NULL)
				{
					continue;
				}
				
				if ($dst_ret["IpType"] == 1 || $dst_ret["IpType"] == 2)
				{
					$dstaddr = " -d ".$dst_ret["IpString"];
				}
				else if ($dst_ret["IpType"] == 0)
				{
					$dstaddr = " -m iprange --dst-range ". $dst_ret["IpString"];
				}
				else
				{
					$dstaddr = " ";
				}
				if ($ret['Log'] == 1){	
					$command .= $iptables. $table. $indev. $srcaddr. $srvtype. $pro_l7. $outdev. $dstaddr. $log. ";";
				}
				$command .= $iptables. $table. $indev. $srcaddr. $srvtype. $pro_l7. $outdev. $dstaddr. $operate. ";";
			}
		}
	}
	//print $command;
	$ret = shell_exec($command);
	//$ret = shell_exec($ext_command);
	return $ret;
}
?>
